﻿using System;
using System.Collections.Generic;
using System.Data;
using System.Text;

namespace Apewer.Source
{

    /// <summary>数据库客户端。</summary>
    public interface IDbOrm
    {

        #region object

        /// <summary>初始化指定类型，以创建表或增加字段。</summary>
        /// <param name="model">要初始化的类型。</param>
        /// <param name="table">指定新的表名。</param>
        /// <returns>错误信息。当成功时候返回空字符串。</returns>
        public string Initialize(Type model, string table = null);

        /// <summary>初始化指定类型，以创建表或增加字段。</summary>
        /// <param name="table">指定新的表名。</param>
        /// <returns>错误信息。当成功时候返回空字符串。</returns>
        public string Initialize<T>(string table = null) where T : class, new();

        /// <summary>插入记录。</summary>
        /// <param name="record">要插入的记录实体。</param>
        /// <param name="table">插入到指定表。当不指定时，由 record 类型决定。</param>
        /// <param name="adjust">调整数据模型，补充缺少的属性。</param>
        /// <returns>错误信息。当成功时候返回空字符串。</returns>
        public string Insert(object record, string table = null, bool adjust = true);

        /// <summary>使用指定语句查询，获取查询结果。</summary>
        /// <param name="model">目标记录的类型。</param>
        /// <param name="sql">要执行的 SQL 语句。</param>
        /// <param name="parameters">为 SQL 命令提供参数。</param>
        /// <exception cref="ArgumentNullException"></exception>
        /// <exception cref="ArgumentException"></exception>
        /// <exception cref="ModelException"></exception>
        /// <exception cref="SqlException"></exception>
        public object[] Query(Type model, string sql, IEnumerable<IDataParameter> parameters = null);

        /// <summary>使用指定语句查询，获取查询结果。</summary>
        /// <param name="sql">要执行的 SQL 语句。</param>
        /// <param name="parameters">为 SQL 命令提供参数。</param>
        /// <exception cref="ArgumentNullException"></exception>
        /// <exception cref="ArgumentException"></exception>
        /// <exception cref="ModelException"></exception>
        /// <exception cref="SqlException"></exception>
        public T[] Query<T>(string sql, IEnumerable<IDataParameter> parameters = null) where T : class, new();

        #endregion

        #region record

        /// <summary>更新记录。</summary>
        /// <param name="record">要插入的记录实体。</param>
        /// <param name="table">插入到指定表。当不指定时，由 record 类型决定。</param>
        /// <param name="adjust">调整数据模型，补充缺少的属性。</param>
        /// <returns>错误信息。当成功时候返回空字符串。</returns>
        public string Update(IRecord record, string table = null, bool adjust = true);

        /// <summary>获取指定类型的主键，按 Flag 属性筛选。</summary>
        /// <param name="model">要查询的类型。</param>
        /// <param name="flag">要求目标记录具有的 Flag 属性，当指定 0 时忽略此要求。</param>
        /// <exception cref="ArgumentNullException"></exception>
        /// <exception cref="ModelException"></exception>
        /// <exception cref="SqlException"></exception>
        public string[] Keys(Type model, long flag = 0);

        /// <summary>获取指定类型的主键，按 Flag 属性筛选。</summary>
        /// <param name="flag">要求目标记录具有的 Flag 属性，当指定 0 时忽略此要求。</param>
        /// <exception cref="ModelException"></exception>
        /// <exception cref="SqlException"></exception>
        public string[] Keys<T>(long flag = 0) where T : class, IRecord, new();

        /// <summary>获取具有指定 Key 的记录，并要求记录具有指定的 Flag 属性。</summary>
        /// <param name="model">目标记录的类型。</param>
        /// <param name="key">目标记录的主键。</param>
        /// <param name="flag">要求目标记录具有的 Flag 属性，当指定 0 时忽略此要求。</param>
        /// <exception cref="ArgumentNullException"></exception>
        /// <exception cref="ModelException"></exception>
        /// <exception cref="SqlException"></exception>
        public object Get(Type model, string key, long flag = 0);

        /// <summary>获取具有指定 Key 的记录，并要求记录具有指定的 Flag 属性。</summary>
        /// <param name="key">目标记录的主键。</param>
        /// <param name="flag">要求目标记录具有的 Flag 属性，当指定 0 时忽略此要求。</param>
        /// <exception cref="ModelException"></exception>
        /// <exception cref="SqlException"></exception>
        public T Get<T>(string key, long flag = 0) where T : class, IRecord, new();

        /// <summary>查询所有记录。</summary>
        /// <param name="model">目标记录的类型。</param>
        /// <param name="flag">要求目标记录具有的 Flag 属性，当指定 0 时忽略此要求。</param>
        /// <exception cref="ArgumentNullException"></exception>
        /// <exception cref="ModelException"></exception>
        /// <exception cref="SqlException"></exception>
        public object[] List(Type model, long flag = 0);

        /// <summary>查询所有记录。</summary>
        /// <param name="flag">要求目标记录具有的 Flag 属性，当指定 0 时忽略此要求。</param>
        /// <exception cref="ModelException"></exception>
        /// <exception cref="SqlException"></exception>
        public T[] List<T>(long flag = 0) where T : class, IRecord, new();

        #endregion

    }

}
